package com.gjxx.netty.codec;

import com.gjxx.common.tcp.*;
import com.gjxx.netty.req.*;
import com.gjxx.netty.resp.ServerCommonRespMsgBody;
import com.gjxx.netty.resp.TerminalRegisterMsgRespBody;

import java.util.Arrays;


public class MsgEncoder {
    private BitOperator bitOperator;
    private JT808ProtocolUtils jt808ProtocolUtils;

    public MsgEncoder() {
        this.bitOperator = new BitOperator();
        this.jt808ProtocolUtils = new JT808ProtocolUtils();
    }

    public byte[] encode4TerminalRegisterResp(TerminalRegisterMsg req, TerminalRegisterMsgRespBody respMsgBody,
                                              int flowId) throws Exception {
        // 消息体字节数组
        byte[] msgBody = null;
        // 鉴权码(STRING) 只有在成功后才有该字段
        if (respMsgBody.getReplyCode() == TerminalRegisterMsgRespBody.success) {
            msgBody = this.bitOperator.concatAll(Arrays.asList(//
                    bitOperator.integerTo2Bytes(respMsgBody.getReplyFlowId()), // 流水号(2)
                    new byte[] { respMsgBody.getReplyCode() }, // 结果
                    respMsgBody.getReplyToken().getBytes(TPMSConsts.string_charset)// 鉴权码(STRING)
            ));
        } else {
            msgBody = this.bitOperator.concatAll(Arrays.asList(//
                    bitOperator.integerTo2Bytes(respMsgBody.getReplyFlowId()), // 流水号(2)
                    new byte[] { respMsgBody.getReplyCode() }// 错误代码
            ));
        }

        // 消息头
        int msgBodyProps = this.jt808ProtocolUtils.generateMsgBodyProps(msgBody.length, 0b000, false, 0);
        byte[] msgHeader = this.jt808ProtocolUtils.generateMsgHeader(req.getMsgHeader().getTerminalPhone(),
                TPMSConsts.msg_id_terminal_register_resp, msgBody, msgBodyProps, flowId);
        byte[] headerAndBody = BitOperator.concatAll(msgHeader, msgBody);

        // 校验码
//        int checkSum = this.bitOperator.getCheckSum4JT808(headerAndBody, 0, headerAndBody.length - 1);
        // 校验码
        byte checkSum = this.bitOperator.getCheckSum4JT808Down(headerAndBody);
        // 连接并且转义
        return this.doEncode(headerAndBody, checkSum);
    }

    public byte[] encode4ServerCommonRespMsg(PackageData req, ServerCommonRespMsgBody respMsgBody, int flowId)
            throws Exception {
        byte[] msgBody = this.bitOperator.concatAll(Arrays.asList(//
                bitOperator.integerTo2Bytes(respMsgBody.getReplyFlowId()), // 应答流水号
                bitOperator.integerTo2Bytes(respMsgBody.getReplyId()), // 应答ID,对应的终端消息的ID
                new byte[] { respMsgBody.getReplyCode() }// 结果
        ));

        // 消息头
        int msgBodyProps = this.jt808ProtocolUtils.generateMsgBodyProps(msgBody.length, 0b000, false, 0);
        byte[] msgHeader = this.jt808ProtocolUtils.generateMsgHeader(req.getMsgHeader().getTerminalPhone(),
                TPMSConsts.cmd_common_resp, msgBody, msgBodyProps, flowId);
        byte[] headerAndBody = BitOperator.concatAll(msgHeader, msgBody);
        // 校验码
//        int checkSum = this.bitOperator.getCheckSum4JT808(headerAndBody, 0, headerAndBody.length - 1);
        byte checkSum = this.bitOperator.getCheckSum4JT808Down(headerAndBody);
        // 连接并且转义
        return this.doEncode(headerAndBody, checkSum);
    }

    public byte[] encodeMediaFileRespMsg(PackageData req, byte[] msgBody, int flowId)
            throws Exception {
//        byte[] msgBody = new byte[]{};
//        if(respMsgBody.getTmpList() == null || respMsgBody.getTmpList().size() == 0){
//            if(respMsgBody.getTempCount() == null){
//                msgBody = this.bitOperator.concatAll(Arrays.asList(//
//                        bitOperator.integerTo2Bytes(respMsgBody.getFileId()) // 文件ID
//                ));
//            }else{
//                msgBody = this.bitOperator.concatAll(Arrays.asList(//
//                        bitOperator.integerTo2Bytes(respMsgBody.getFileId()), // 文件ID
//                        respMsgBody.getTempCount() // 重传包总数
//                ));
//            }
//        }else {
//            msgBody = this.bitOperator.concatAll(Arrays.asList(//
//                    bitOperator.integerTo2Bytes(respMsgBody.getFileId()), // 文件ID
//                    respMsgBody.getTempCount(), // 重传包总数
//                    bitOperator.concatAll(respMsgBody.getTmpList()) // 重传包ID列表
//            ));
//        }
        // 消息头
        int msgBodyProps = this.jt808ProtocolUtils.generateMsgBodyProps(msgBody.length, 0b000, false, 0);
        byte[] msgHeader = this.jt808ProtocolUtils.generateMsgHeader(req.getMsgHeader().getTerminalPhone(),
                TPMSConsts.cmd_media_file_upload_resp, msgBody, msgBodyProps, flowId);
        byte[] headerAndBody = BitOperator.concatAll(msgHeader, msgBody);
        // 校验码
        byte checkSum = this.bitOperator.getCheckSum4JT808Down(headerAndBody);
        // 连接并且转义
        return this.doEncode(headerAndBody, checkSum);
    }

    public byte[] encode4ParamSetting(byte[] msgBodyBytes, String phone,int command,int flowId) throws Exception {
        // 消息头
        int msgBodyProps = this.jt808ProtocolUtils.generateMsgBodyProps(msgBodyBytes.length, 0b000, false, 0);
        byte[] msgHeader = this.jt808ProtocolUtils.generateMsgHeader(phone,
                command, msgBodyBytes, msgBodyProps, flowId);
        // 连接消息头和消息体
        byte[] headerAndBody = BitOperator.concatAll(msgHeader, msgBodyBytes);
        // 校验码
//        int checkSum = this.bitOperator.getCheckSum4JT808(headerAndBody, 0, headerAndBody.length - 1);
        byte checkSum = this.bitOperator.getCheckSum4JT808Down(headerAndBody);
        // 连接并且转义
        return this.doEncode(headerAndBody, checkSum);
    }

    private byte[] doEncode(byte[] headerAndBody, byte checkSum) throws Exception {
        byte[] noEscapedBytes = this.bitOperator.concatAll(Arrays.asList(//
                new byte[] { TPMSConsts.pkg_delimiter }, // 0x7e
                headerAndBody, // 消息头+ 消息体
                new byte[] { checkSum }, // 校验码
                new byte[] { TPMSConsts.pkg_delimiter }// 0x7e
        ));
        // 转义
        return jt808ProtocolUtils.doEscape4Send(noEscapedBytes, 1, noEscapedBytes.length - 1);
    }
}
